Skip to content

fix: fall back to getent for users that are not findable in /etc/passwd#183

Merged
tonyandrewmeyer merged 8 commits into
canonical:mainfrom
tonyandrewmeyer:fix-username-lookup-no-passwd
May 19, 2026
Merged

fix: fall back to getent for users that are not findable in /etc/passwd#183
tonyandrewmeyer merged 8 commits into
canonical:mainfrom
tonyandrewmeyer:fix-username-lookup-no-passwd

Conversation

@tonyandrewmeyer
Copy link
Copy Markdown
Contributor

@tonyandrewmeyer tonyandrewmeyer commented Apr 15, 2026

The go User.Lookup method on Unix-like systems without ego just looks in the /etc/password file (whereas cgo does a getpwnam check via libc). On some systems, like the Canonical laptops, the user that is trying to run Concierge may not be in /etc/passwd and be loaded from a directory service instead.

This PR adds a fallback system where we will run the getent binary. That comes from the libc-bin package in Ubuntu, so is very likely to be available (and the worst case is that it's not and we'll fail just as we did before).

Fixes #182

@tonyandrewmeyer
Copy link
Copy Markdown
Contributor Author

FYI, you can test this with the --dry-run argument on a Canonical laptop. With the latest release (or main) you should get an error before Concierge manages to do anything. With this branch (sudo go run ./main.py prepare -p dev --dry-run) you should see the normal dry-run output. You won't see the call to getent because that happens so early (there's a comment that explains this); I looked into using that instead but it made it quite complex for almost no benefit.

@tonyandrewmeyer tonyandrewmeyer marked this pull request as ready for review April 16, 2026 02:02
Copy link
Copy Markdown
Contributor

@dimaqq dimaqq left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fly-by: the change looks good to me.

Copy link
Copy Markdown
Contributor

@james-garner-canonical james-garner-canonical left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Landing this as-is seems reasonable to me.

I do wonder if we should swallow all errors from trying to run getent the way we are, and also if we should have a test exercising how we fail if getent isn't available.

I don't think these should block landing this feature since Ubuntu should always have getent and 'user not found' is probably our only expected error.

Comment thread internal/system/util.go Outdated
Comment thread internal/system/util_test.go
tonyandrewmeyer and others added 2 commits May 19, 2026 14:19
Previously any error from `getent passwd` — including the binary being
missing or NSS misconfiguration — was reported as "unknown user", hiding
the real cause. Inspect the exit code: 2 ("key not found") maps to
`user.UnknownUserError` so callers can still match it with errors.As;
anything else is wrapped with %w. Malformed output is also surfaced
verbatim rather than masquerading as an unknown user.

Add a `getentBinary` package variable so tests can simulate the binary
being absent, and add a test that exercises that path. Tighten the
existing unknown-user test to assert the typed error.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@tonyandrewmeyer tonyandrewmeyer merged commit 5b915d8 into canonical:main May 19, 2026
39 checks passed
@tonyandrewmeyer tonyandrewmeyer deleted the fix-username-lookup-no-passwd branch May 19, 2026 02:54
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Prepare does not work for users that are not in /etc/passwd

3 participants